package com.zyk.scaffold.user.mail.components;

import com.alibaba.fastjson.JSON;
import com.zyk.scaffold.common.utils.AssertUtil;
import com.zyk.scaffold.user.dto.MailMessageDTO;
import com.zyk.scaffold.user.mail.AccountMailSenderManager;
import com.zyk.scaffold.user.mail.properties.LocalMailProperties;
import com.zyk.scaffold.user.mail.sender.ILocalMailSender;
import com.zyk.scaffold.user.mail.sender.SenderMessage;
import freemarker.template.Configuration;
import freemarker.template.Template;
import freemarker.template.TemplateException;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;
import org.springframework.ui.freemarker.FreeMarkerTemplateUtils;
import org.springframework.util.CollectionUtils;

import javax.annotation.Resource;
import java.io.IOException;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.Map;

@Slf4j
@Component
public class MailComponent {

    /**
     * 用来发送模版邮件
     */
    @Resource
    private Configuration freemarkerConfiguration;

    @Autowired
    private LocalMailProperties localMailProperties;

    @Autowired
    private AccountMailSenderManager accountMailSenderManager;

    public boolean send(MailMessageDTO mailMessageDTO) {
        if(!valid(mailMessageDTO)){
            log.error("邮件发送,参数校验不通过：{}", JSON.toJSONString(mailMessageDTO));
            AssertUtil.error("邮件发送,参数校验不通过");
        }
        ILocalMailSender mailSender = accountMailSenderManager.getMailSender(localMailProperties.getUseName());
        if (null == mailSender){
            log.error("邮件发送失败，账号配置不存在：{}", localMailProperties.getUseName());
            AssertUtil.error("邮件发送失败，账号配置不存在");
        }
        Map<String, String> templatesMapping = localMailProperties.getTemplate();
        if (null == templatesMapping.get(mailMessageDTO.getTemplateCode())){
            log.error("邮件发送失败，选择的模板不存在：{}", JSON.toJSONString(mailMessageDTO));
            AssertUtil.error("邮件发送失败，选择的模板不存在");
        }
        try {
            Template template = freemarkerConfiguration.getTemplate(templatesMapping.get(mailMessageDTO.getTemplateCode()));
            Map<String, Object> templateData = mailMessageDTO.getTemplateData();
            String emailContent = FreeMarkerTemplateUtils.processTemplateIntoString(template, templateData);
            String subject = buildSbuject(mailMessageDTO.getSubject());
            SenderMessage senderMessage = new SenderMessage();
            senderMessage.setFrom(localMailProperties.getSendEmail());
            senderMessage.setTo(mailMessageDTO.getTo());
            senderMessage.setSubject(subject);
            senderMessage.setContent(emailContent);
            boolean send = mailSender.send(senderMessage);
            if(send){
                log.info("【成功】- 邮件发送完成,\n 预警邮件类型:{},\n 发送时间:{},\n 邮件主题：{},\n 邮件内容：{},\n 收件人:{}"
                        , mailMessageDTO.getTemplateCode()
                        , LocalDateTime.now().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"))
                        , subject
                        , JSON.toJSONString(mailMessageDTO.getTemplateData())
                        , JSON.toJSONString(mailMessageDTO.getTo()));
            }
            return send;
        } catch (IOException | TemplateException e) {
            log.error("邮件发送失败,参数：" + JSON.toJSONString(mailMessageDTO), e);
            AssertUtil.error("邮件发送失败");
        }catch (Exception e){
            log.error("邮件发送出现异常,参数：" + JSON.toJSONString(mailMessageDTO), e);
            AssertUtil.error("邮件发送出现异常");
        }
        return false;
    }

    private String buildSbuject(String subject) {
        String subjectPrefix = localMailProperties.getSubjectPrefix();
        if(StringUtils.isNotEmpty(subjectPrefix)){
            return subjectPrefix + subject;
        }
        return subject;
    }

    private boolean valid(MailMessageDTO mailMessageDTO){
        return !(mailMessageDTO == null
                || null == mailMessageDTO.getTo()
                || mailMessageDTO.getTo().length == 0
                || StringUtils.isEmpty(mailMessageDTO.getSubject())
                || CollectionUtils.isEmpty(mailMessageDTO.getTemplateData())
                || null == mailMessageDTO.getTemplateCode());
    }

}
